﻿#include "CRegMgr.h"
#include "DeclareDefine.h"

CRegTypeItem::CRegTypeItem() {}

CRegTypeItem::~CRegTypeItem() { RemoveAll(); }

void CRegTypeItem::PreVecObjRemove(const IRegisterPtr &obj) {
  if (obj) {
    delete obj;
  }
}

bool CRegTypeItem::EqualVecObj(const IRegisterPtr &objsrc,
                               const IRegisterPtr &objdest) const {
  return (0 == _wcsicmp(objsrc->GetRegItemName(), objdest->GetRegItemName()));
}

std::wstring &CRegTypeItem::GetDefRegName() { return m_strDefRegName; }

CRegMgr::CRegMgr() {}

CRegMgr::~CRegMgr() { RemoveAll(); }
void CRegMgr::PreMapKeyRemove(const CRegTypeItemPtr &obj) {
  if (obj) {
    delete obj;
  }
}

int CRegMgr::Register(IRegister &RegObj, bool bReplace /*= false*/,
                      bool bSetDefName /*= true*/) {
  int iRet = -1;
  do {
    CRegTypeItemPtr pRegItem = NULL;
    int RegType = RegObj.GetRegType();
    if (!GetObjByKey(RegType, pRegItem)) {
      // 不存在
      pRegItem = new CRegTypeItem;
      AddKey(RegType, pRegItem);
    }

    int iElement = pRegItem->FindObj(&RegObj);
    if (-1 != iElement) {
      // 已经存在
      if (bReplace) {
        pRegItem->RemoveObj(iElement);
      } else {
        iRet = -2;
        break;
      }
    }

    if (pRegItem->AddObj(RegObj.Clone())) {
      // success
      iRet = 0;
      if (bSetDefName) {
        pRegItem->GetDefRegName() = SAFE_STR(RegObj.GetRegItemName());
      }
    }
  } while (FALSE);
  return iRet;
}

int CRegMgr::CreateRegObj(void **ppObj, LPCWSTR lpszRegName, int RegType) {
  int iErr = -1;
  do {
    CRegTypeItemPtr pRegItem = NULL;
    if (!GetObjByKey(RegType, pRegItem)) {
      break;
    }
    if (NULL == lpszRegName || 0 == wcslen(lpszRegName)) {
      lpszRegName = pRegItem->GetDefRegName().c_str();
    }

    if (NULL == ppObj) {
      // assert("您传的不是双指针！");
      iErr = -2;
      break;
    }

    if (NULL == lpszRegName) {
      // assert("您没设置类名啊！");
      iErr = -3;
      break;
    }

    int count = (int)pRegItem->GetCount();
    if (0 == count) {
      // 注册数量是0
      iErr = -4;
      break;
    }

    for (int i = 0; i < count; i++) {
      if (0 == _wcsicmp(lpszRegName, pRegItem->GetObj(i)->GetRegItemName())) {
        *ppObj = (void **)(pRegItem->GetObj(i)->NewObj());
        iErr = 0;
        break;
      }
    }
  } while (FALSE);
  return iErr;
}

int CRegMgr::UnRegister(LPCWSTR lpszRegName, int RegType) {
  int iErr = -1;
  do {
    CRegTypeItemPtr pRegItem = NULL;
    if (!GetObjByKey(RegType, pRegItem)) {
      // 没有注册
      break;
    }

    int count = (int)pRegItem->GetCount();
    for (int i = 0; i < count; i++) {
      if (0 == _wcsicmp(lpszRegName, pRegItem->GetObj(i)->GetRegItemName())) {
        pRegItem->RemoveObj(i);
        iErr = 0;
        break;
      }
    }
  } while (FALSE);
  return iErr;
}

int CRegMgr::SetDefRegObj(LPCWSTR lpszRegName, int RegType) {
  int iErr = -1;
  do {
    if (!lpszRegName) {
      break;
    }

    CRegTypeItemPtr pRegItem = NULL;
    if (!GetObjByKey(RegType, pRegItem)) {
      // 没有注册
      break;
    }

    if (lpszRegName == pRegItem->GetDefRegName()) {
      // 相同的默认名称
      iErr = 1;
      break;
    }

    int count = (int)pRegItem->GetCount();
    for (int i = 0; i < count; i++) {
      if (0 == _wcsicmp(lpszRegName, pRegItem->GetObj(i)->GetRegItemName())) {
        pRegItem->GetDefRegName() = SAFE_STR(lpszRegName);
        iErr = 0;
        break;
      }
    }
  } while (FALSE);
  return iErr;
}

int CRegMgr::GetDefRegObj(std::wstring &lpszRegName, int RegType) {
  int iErr = -1;
  do {
    CRegTypeItemPtr pRegItem = NULL;
    if (!GetObjByKey(RegType, pRegItem)) {
      // 没有注册
      break;
    }
    lpszRegName = pRegItem->GetDefRegName();
    iErr = 0;
  } while (FALSE);
  return iErr;
}
